﻿//#define DEBUG
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Net.Sockets;
using System.Net;
using System.Collections;
using System.Threading;
using System.Globalization;
using Model;
using GameHelp;
using System.IO;
using helper;
using Intorise.Tools.Process;
using System.Diagnostics;
using Common;
using Database;

namespace TdyxAutoBot
{
    delegate void CreateTextbox(ConnectionMap map);
    delegate void WriterMessage(RichTextBox textBox, string message);

    public partial class MainForm : Form
    {
        #region private data
        TcpListener listener80;
        TcpListener listener443;
        TcpListener listener843;
        TcpListener listener8000;
        TcpListener listener8001;
        TcpListener listener8010;
        TcpClient sendClient80;
        TcpClient sendClient443;
        TcpClient sendServer8000Tcp;
        TcpClient sendServer8001Tcp;
        TcpClient sendClientFrom8001Tcp;
        TcpClient sendServer8010Tcp;
        TcpClient sendClientFrom8010Tcp;
        AsyncCallback callback80;
        AsyncCallback callback443;
        AsyncCallback callback843;
        AsyncCallback callback8000;
        AsyncCallback serverDataRead;
        AsyncCallback clientDataRead;
        string ServerHost = "123.58.145.177";
        int GamePort = 3320;
        Hashtable clientTable = new Hashtable();
        Hashtable userClientTable = new Hashtable();
        Hashtable characterTxtboxMap = new Hashtable();
        Dictionary<Account, Process> loginFormDict = new Dictionary<Account, Process>();
        object txtMessageLocker = new object();//用于世界显示的线程锁
        byte[] charectorNameTag = new byte[] { 0x00, 0xff, 0x10, 0x00, 0x00, 0x00, 0x00 };//角色名称数据包前缀
        string policy = "<?xml version=\"1.0\"?><cross-domain-policy><allow-access-from domain=\"*\" to-ports=\"*\" /></cross-domain-policy>\0";
        string policyRequest = "<policy-file-request/>";
        #endregion

        bool log80 = true;
        bool log843 = true;
        bool log8000 = true;
        bool log8001 = true;
        bool keeped = false;
        object locker = new object();
        Thread keepConnectThread = null;

        public MainForm()
        {
            InitializeComponent();
            Form.CheckForIllegalCrossThreadCalls = false;
            callback80 = new AsyncCallback(callback80Method);
            callback843 = new AsyncCallback(callback843Method);
            callback8000 = new AsyncCallback(callback8000Method);
            sendClient443 = new TcpClient();

            keepConnectThread = new Thread(new ParameterizedThreadStart(delegate(object obj)
            {
                byte[] array = new byte[] { 0x09, 0x00, 0x01, 0x01, 0x00, 0x19, 0x1D, 0x00, 0x04 };
                while (true)
                {
                    try
                    {
                        TcpHelper.Forward(sendServer8001Tcp, array, array.Length);
                        PrintMessage("Keep server 8001 connected.");
                    }
                    catch (Exception ex)
                    {
                        LogAndPrint("出现错误，已与服务器8001失去连接。");
                        Tools.PrintException(ex);
                    }
                    Thread.Sleep(3000);
                }
            }));

            IPEndPoint localEndPoint80 = new IPEndPoint(IPAddress.Parse("127.0.0.1"), 80);
            IPEndPoint localEndPoint443 = new IPEndPoint(IPAddress.Parse("127.0.0.1"), 443);
            IPEndPoint localEndPoint843 = new IPEndPoint(IPAddress.Parse("127.0.0.1"), 843);
            IPEndPoint localEndPoint8000 = new IPEndPoint(IPAddress.Parse("127.0.0.1"), 8000);
            IPEndPoint localEndPoint8001 = new IPEndPoint(IPAddress.Parse("127.0.0.1"), 8001);
            IPEndPoint localEndPoint8010 = new IPEndPoint(IPAddress.Parse("127.0.0.1"), 8010);

            listener80 = new TcpListener(localEndPoint80);
            listener443 = new TcpListener(localEndPoint443);
            listener843 = new TcpListener(localEndPoint843);
            listener8000 = new TcpListener(localEndPoint8000);
            listener8001 = new TcpListener(localEndPoint8001);
            listener8010 = new TcpListener(localEndPoint8010);

            listener80.Start();
            listener443.Start();
            listener843.Start();
            listener8000.Start();
            listener8001.Start();
            listener8010.Start();
            listener80.BeginAcceptTcpClient(callback80, listener80);
            listener443.BeginAcceptTcpClient(callback443, listener443);
            listener843.BeginAcceptTcpClient(callback843, listener843);
            listener8000.BeginAcceptTcpClient(callback8000, listener8000);
            listener8001.BeginAcceptTcpClient(callbackMethod, new ListenerStateObject { Listener = listener8001, Port = 8001, ClientDataCallback = ReciveClientData, ServerDataCallback = ReciveServerData });
            listener8010.BeginAcceptTcpClient(callbackMethod, new ListenerStateObject { Listener = listener8010, Port = 8010, ClientDataCallback = ReciveClientData, ServerDataCallback = ReciveServerData });
            LogAndPrint("开始监听80.\r\n开始监听443.\r\n开始监听843.\r\n开始监听8000.\r\n开始监听8001.\r\n开始监听8001.");
        }

        //启动登录窗口，登录所有账户
        private void StartLoginForm(object o)
        {
            foreach (Account account in Manager.AccountList)
            {
                GameConfig config = Manager.GetConfig(account);
                if (config != null && config.AutoLogin)
                {
                    Log("账户：" + account.Username + " 开始自动登录...");
                    Process p = new Process();
                    //助手窗口标题，账户，密码，角色名，平台，服务器编号
                    p.StartInfo = new ProcessStartInfo("Client.exe", this.Text + " " + account.Username + " " + account.Password + " " + account.Character.Name + " " + account.Chanel + " " + account.ServerID);
                    p.Start();
                    loginFormDict.Add(account, p);
                    Thread.Sleep(10000);//等待15秒后在进行下一个账户的登录
                }
            }
        }

        private void callbackMethod(IAsyncResult result)
        {
            if (result == null) { return; }
            ListenerStateObject state = (ListenerStateObject)result.AsyncState;
            if (state == null) { return; }

            state.Listener.BeginAcceptTcpClient(callbackMethod, state);
            LogAndPrint("接收到" + state.Port + "请求");
            TcpClient client = state.Listener.EndAcceptTcpClient(result);
            sendClientFrom8001Tcp = client;
            TcpClient sendclient = new TcpClient();
            sendclient.Connect(ServerHost, state.Port);
            sendServer8001Tcp = sendclient;
            LogAndPrint("建立到服务端" + state.Port + "连接...");

            NetworkStream streamRecive = client.GetStream();
            StateObject stateObject = new StateObject(client, sendclient, state.Port);
            streamRecive.BeginRead(stateObject.Buffer, 0, stateObject.Buffer.Length, state.ClientDataCallback, stateObject);
            LogAndPrint("开始读取客户端" + state.Port + "数据.");

            NetworkStream streamSend = sendclient.GetStream();
            stateObject = new StateObject(client, sendclient, state.Port);
            streamSend.BeginRead(stateObject.Buffer, 0, stateObject.Buffer.Length, state.ServerDataCallback, stateObject);
            LogAndPrint("开始读取服务端返回" + state.Port + "的数据...");
        }

        private void callback80Method(IAsyncResult result)
        {
            listener80.BeginAcceptTcpClient(callback80, listener80);
            if (log80) LogAndPrint("接收到80请求");
            TcpClient client = listener80.EndAcceptTcpClient(result);
            TcpClient sendclient = new TcpClient();
            sendclient.Connect(ServerHost, 80);
            if (log80) LogAndPrint("建立到服务端80连接...");

            NetworkStream streamRecive = client.GetStream();
            StateObject state = new StateObject(client, sendclient);
            streamRecive.BeginRead(state.Buffer, 0, state.Buffer.Length, ReciveClient80Data, state);
            if (log80) LogAndPrint("开始读取客户端80数据.");

            NetworkStream streamSend = sendclient.GetStream();
            state = new StateObject(client, sendclient);
            streamSend.BeginRead(state.Buffer, 0, state.Buffer.Length, ReciveServer80Data, state);
            if (log80) LogAndPrint("开始读取服务端返回80的数据...");
        }

        private void callback843Method(IAsyncResult result)
        {
            listener843.BeginAcceptTcpClient(callback843, listener843);
            if (log843) LogAndPrint("接收到843请求");
            TcpClient client = listener843.EndAcceptTcpClient(result);
            TcpClient sendclient = new TcpClient();
            sendclient.Connect(ServerHost, 843);
            if (log843) LogAndPrint("建立到服务端843连接...");

            NetworkStream streamRecive = client.GetStream();
            StateObject state = new StateObject(client, sendclient);
            streamRecive.BeginRead(state.Buffer, 0, state.Buffer.Length, ReciveClient843Data, state);
            if (log843) LogAndPrint("开始读取客户端843数据.");

            NetworkStream streamSend = sendclient.GetStream();
            state = new StateObject(client, sendclient);
            streamSend.BeginRead(state.Buffer, 0, state.Buffer.Length, ReciveServer843Data, state);
            if (log843) LogAndPrint("开始读取服务端返回843的数据...");
        }

        //登录
        private void callback8000Method(IAsyncResult result)
        {
            listener8000.BeginAcceptTcpClient(callback8000, listener8000);
            if (log8000) LogAndPrint("接收到8000请求");
            TcpClient client = listener8000.EndAcceptTcpClient(result);
            sendServer8000Tcp = new TcpClient();
            sendServer8000Tcp.Connect(ServerHost, 8000);
            if (log8000) LogAndPrint("建立到服务端8000连接...");

            NetworkStream streamRecive = client.GetStream();
            StateObject state = new StateObject(client, sendServer8000Tcp);
            streamRecive.BeginRead(state.Buffer, 0, state.Buffer.Length, ReciveClient8000Data, state);
            if (log8000) LogAndPrint("开始读取客户端8000数据.");

            NetworkStream streamSend = sendServer8000Tcp.GetStream();
            state = new StateObject(client, sendServer8000Tcp);
            streamSend.BeginRead(state.Buffer, 0, state.Buffer.Length, ReciveServer8000Data, state);
            if (log8000) LogAndPrint("开始读取服务端返回8000的数据...");
        }

        //当获取到角色等级信息可以自动游戏时进行关闭客户端等操作
        private void Operationer_OnConnected(Account account)
        {
            GameConfig config = Manager.GetConfig(account);

            if (config.AutoLogin && loginFormDict.ContainsKey(account))
            {
                switch (config.WindowState)
                {
                    case ClientWindowState.Hide:
                        ProcessMessage.SendMessage(loginFormDict[account].MainWindowTitle, "NeedHide");
                        Console.WriteLine(account.Character.Name + " 的客户端窗口已隐藏");
                        this.btnShowClient.Enabled = true;
                        break;
                    case ClientWindowState.Close:
                        loginFormDict[account].Kill();
                        Console.WriteLine(account.Character.Name + " 的客户端窗口已关闭");
                        this.btnStartClient.Enabled = true;
                        loginFormDict.Remove(account);
                        break;
                }
            }
        }

        //客户端数据处理
        private void ReciveClientData(IAsyncResult result)
        {
            if (result == null) { return; }
            StateObject state = (StateObject)result.AsyncState;
            if (state == null) { return; }
            TcpClient client = state.Client;
            TcpClient serverClient = state.Server;
            NetworkStream clientStrem = null;
            int length = 0;

            try
            {
                clientStrem = client.GetStream();
                length = clientStrem.EndRead(result);
            }
            catch (Exception ex)
            {
                LogAndPrint("读取客户端" + state.Port + "数据出现错误，客户端连接可能已关闭");
                Tools.PrintException(ex);
                lock (locker)
                {
                    if (!keeped)
                    {
                        keeped = true;
                        keepConnectThread.Start();
                    }
                }
                return;
            }

            if (length > 0)//有数据
            {
                if (log8001) PrintData("C->S:" + state.Port, state.Buffer, length);
                #region 转发到服务端
                if (serverClient.Connected)
                {
                    try
                    {
                        NetworkStream serverStrem = serverClient.GetStream();
                        serverStrem.Write(state.Buffer, 0, length);
                        //if (log8001) Log("转发到服务端" + state.Port);
                    }
                    catch
                    {
                        LogAndPrint("转发到服务端" + state.Port + "出现错误，服务端连接可能已关闭");
                    }
                }
                #endregion
            }
            //继续异步接收数据
            //Thread.Sleep(100);
            state = new StateObject(client, serverClient, state.Port);
            try
            {
                clientStrem.BeginRead(state.Buffer, 0, state.Buffer.Length, ReciveClientData, state);
            }
            catch (Exception ex)
            {
                LogAndPrint("读取客户端" + state.Port + "数据出现错误，客户端连接可能已关闭");
                Tools.PrintException(ex);
                lock (locker)
                {
                    if (!keeped)
                    {
                        keeped = true;
                        keepConnectThread.Start();
                    }
                }
            }
        }

        //服务端返回的数据处理
        private void ReciveServerData(IAsyncResult result)
        {
            if (result == null) { return; }
            StateObject state = (StateObject)result.AsyncState;
            if (state == null) { return; }
            TcpClient client = state.Client;
            TcpClient serverClient = state.Server;
            NetworkStream serverStrem = null;

            try
            {
                serverStrem = serverClient.GetStream();
                int length = serverStrem.EndRead(result);
                if (length > 0)//有数据
                {
                    if (log8001) PrintData("S->C:" + state.Port, state.Buffer, length);
                    //LogAndPrint("S->C: " + state.Port + " length:" + length);
                    #region 转发到客户端
                    if (client.Connected)
                    {
                        try
                        {
                            NetworkStream clientStrem = client.GetStream();
                            clientStrem.Write(state.Buffer, 0, length);
                            //if (log8001) Log("通过" + state.Port + "转发到客户端");
                        }
                        catch (Exception ex)
                        {
                            LogAndPrint("8001转发到客户端出现错误，客户端连接可能已关闭");
                            Tools.PrintException(ex);
                        }
                    }
                    #endregion
                }
                //继续异步接收数据
                //Thread.Sleep(100);
                state = new StateObject(client, serverClient, state.Port);
                serverStrem.BeginRead(state.Buffer, 0, state.Buffer.Length, ReciveServerData, state);
            }
            catch (Exception ex)
            {
                LogAndPrint("出现错误，已与服务器8001失去连接。");
                Tools.PrintException(ex);
            }
        }

        //客户端80数据处理
        private void ReciveClient80Data(IAsyncResult result)
        {
            if (result == null) { return; }
            StateObject state = (StateObject)result.AsyncState;
            if (state == null) { return; }
            TcpClient client = state.Client;
            TcpClient serverClient = state.Server;
            NetworkStream clientStrem = null;

            try
            {
                clientStrem = client.GetStream();
                int length = clientStrem.EndRead(result);
                if (length > 0)//有数据
                {
                    if (log80) PrintData("收到客户端发送到80的数据", state.Buffer, length);
                    #region 转发到服务端
                    if (serverClient.Connected)
                    {
                        try
                        {
                            NetworkStream serverStrem = serverClient.GetStream();
                            serverStrem.Write(state.Buffer, 0, length);
                            if (log80) Log("转发到服务端");
                        }
                        catch
                        {
                            Log("转发到服务端出现错误，服务端连接可能已关闭");
                        }
                    }
                    #endregion
                }
                //继续异步接收数据
                //Thread.Sleep(100);
                state = new StateObject(client, serverClient);
                clientStrem.BeginRead(state.Buffer, 0, state.Buffer.Length, ReciveClient80Data, state);
            }
            catch (Exception ex)
            {
                LogAndPrint("出现错误，已与服务器失去连接。");
                Tools.PrintException(ex);
            }
        }

        //服务端返回的80数据处理
        private void ReciveServer80Data(IAsyncResult result)
        {
            if (result == null) { return; }
            StateObject state = (StateObject)result.AsyncState;
            if (state == null) { return; }
            TcpClient client = state.Client;
            TcpClient serverClient = state.Server;
            NetworkStream serverStrem = null;

            try
            {
                serverStrem = serverClient.GetStream();
                int length = serverStrem.EndRead(result);
                if (length > 0)//有数据
                {
                    if (log80) PrintData("收到服务器80端口返回的数据", state.Buffer, length);
                    #region 转发到客户端
                    if (client.Connected)
                    {
                        try
                        {
                            NetworkStream clientStrem = client.GetStream();
                            clientStrem.Write(state.Buffer, 0, length);
                            if (log80) LogAndPrint("通过80转发到客户端");
                        }
                        catch (Exception ex)
                        {
                            LogAndPrint("转发到客户端出现错误，客户端连接可能已关闭");
                            Tools.PrintException(ex);
                            return;
                        }
                    }
                    #endregion
                }
                //继续异步接收数据
                //Thread.Sleep(100);
                state = new StateObject(client, serverClient);
                serverStrem.BeginRead(state.Buffer, 0, state.Buffer.Length, ReciveServer80Data, state);
            }
            catch (Exception ex)
            {
                LogAndPrint("出现错误，已与服务器失去连接。");
                Tools.PrintException(ex);
            }
        }

        //客户端8000数据处理
        private void ReciveClient8000Data(IAsyncResult result)
        {
            if (result == null) { return; }
            StateObject state = (StateObject)result.AsyncState;
            if (state == null) { return; }
            TcpClient client = state.Client;
            TcpClient serverClient = state.Server;
            NetworkStream clientStrem = null;

            try
            {
                clientStrem = client.GetStream();
                int length = clientStrem.EndRead(result);
                if (length > 0)//有数据
                {
                    if (log8000) PrintData("C->S:8000", state.Buffer, length);
                    #region 转发到服务端
                    if (serverClient.Connected)
                    {
                        try
                        {
                            NetworkStream serverStrem = serverClient.GetStream();
                            serverStrem.Write(state.Buffer, 0, length);
                            if (log8000) LogAndPrint("转发到服务器8000端口");
                        }
                        catch
                        {
                            LogAndPrint("转发到服务端出现错误，服务端连接可能已关闭");
                        }
                    }
                    #endregion
                }
                //继续异步接收数据
                //Thread.Sleep(100);
                state = new StateObject(client, serverClient);
                clientStrem.BeginRead(state.Buffer, 0, state.Buffer.Length, ReciveClient8000Data, state);
            }
            catch (Exception ex)
            {
                LogAndPrint("出现错误，已与服务器失去连接。");
                Tools.PrintException(ex);
            }
        }

        //服务端返回的8000数据处理
        private void ReciveServer8000Data(IAsyncResult result)
        {
            if (result == null) { return; }
            StateObject state = (StateObject)result.AsyncState;
            if (state == null) { return; }
            TcpClient client = state.Client;
            TcpClient serverClient = state.Server;
            NetworkStream serverStrem = null;

            try
            {
                serverStrem = serverClient.GetStream();
                int length = serverStrem.EndRead(result);
                if (length > 0)//有数据
                {
                    //if (log8000) PrintData("S->C:8000", state.Buffer, length);
                    LogAndPrint("S->C:8000 length:" + length);
                    #region 转发到客户端
                    if (client.Connected)
                    {
                        try
                        {
                            NetworkStream clientStrem = client.GetStream();
                            clientStrem.Write(state.Buffer, 0, length);
                            //if (log8000) Log("通过8000端口转发到客户端");
                        }
                        catch (Exception ex)
                        {
                            LogAndPrint("8000数据转发到客户端出现错误，客户端连接可能已关闭");
                            Tools.PrintException(ex);
                        }
                    }
                    #endregion
                }
                //继续异步接收数据
                //Thread.Sleep(100);
                state = new StateObject(client, serverClient);
                serverStrem.BeginRead(state.Buffer, 0, state.Buffer.Length, ReciveServer8000Data, state);
            }
            catch (Exception ex)
            {
                Log("出现错误，已与服务器失去连接。");
                Tools.PrintException(ex);
            }
        }

        //客户端843数据处理
        private void ReciveClient843Data(IAsyncResult result)
        {
            if (result == null) { return; }
            StateObject state = (StateObject)result.AsyncState;
            if (state == null) { return; }
            TcpClient client = state.Client;
            TcpClient serverClient = state.Server;
            NetworkStream clientStrem = null;

            try
            {
                clientStrem = client.GetStream();
                int length = clientStrem.EndRead(result);
                if (length > 0)//有数据
                {
                    if (log843) PrintData("收到客户端发送到843端口的数据", state.Buffer, length);

                    #region 转发到服务端
                    if (serverClient.Connected)
                    {
                        try
                        {
                            NetworkStream serverStrem = serverClient.GetStream();
                            serverStrem.Write(state.Buffer, 0, length);
                            if (log843) LogAndPrint("转发到服务器843");
                        }
                        catch
                        {
                            LogAndPrint("转发到服务器843出现错误，服务端连接可能已关闭");
                        }
                    }
                    #endregion
                }
                //继续异步接收数据
                //Thread.Sleep(100);
                state = new StateObject(client, serverClient);
                clientStrem.BeginRead(state.Buffer, 0, state.Buffer.Length, ReciveClient843Data, state);
            }
            catch (Exception ex)
            {
                LogAndPrint("出现错误，已与服务器失去连接。");
                Tools.PrintException(ex);
            }
        }

        //服务端返回的843数据处理
        private void ReciveServer843Data(IAsyncResult result)
        {
            if (result == null) { return; }
            StateObject state = (StateObject)result.AsyncState;
            if (state == null) { return; }
            TcpClient client = state.Client;
            TcpClient serverClient = state.Server;
            NetworkStream serverStrem = null;

            try
            {
                serverStrem = serverClient.GetStream();
                int length = serverStrem.EndRead(result);
                if (length > 0)//有数据
                {
                    if (log843) PrintData("收到服务器843端口发送来的数据", state.Buffer, length);

                    #region 转发到客户端
                    if (client.Connected)
                    {
                        try
                        {
                            NetworkStream clientStrem = client.GetStream();
                            clientStrem.Write(state.Buffer, 0, length);
                            clientStrem.Flush();
                            if (log843) LogAndPrint("通过843端口转发到客户端");
                        }
                        catch (Exception ex)
                        {
                            //Log("通过843端口转发到客户端出现错误，客户端连接可能已关闭");
                            Tools.PrintException(ex);
                        }
                    }
                    #endregion
                }
                //继续异步接收数据
                //Thread.Sleep(100);
                state = new StateObject(client, serverClient);
                serverStrem.BeginRead(state.Buffer, 0, state.Buffer.Length, ReciveServer843Data, state);
            }
            catch (Exception ex)
            {
                LogAndPrint("出现错误，已与服务器失去连接。");
                Tools.PrintException(ex);
            }
        }

        //查找角色名称
        private string SearchName(byte[] datas, int length)
        {
            string nameTag = UTF8Encoding.UTF8.GetString(charectorNameTag);
            string dataString = UTF8Encoding.UTF8.GetString(datas, 0, length);
            int index = dataString.IndexOf(nameTag);
            if (index > -1)
            {
                return dataString.Substring(10, dataString.Length - 11);
            }
            return "";
        }

        //查找账户的平台和服务器信息
        private Account SearchAccount(byte[] datas, int length)
        {
            string dataString = UTF8Encoding.UTF8.GetString(datas, 0, length);
            int index = dataString.LastIndexOf('\0');//数据最后一个0x00的后面是平台和服务器信息
            if (index > -1)
            {
                Account account = new Account();
                string[] info = dataString.Substring(index + 1).Split(new char[] { '_' }, StringSplitOptions.RemoveEmptyEntries);
                if (info.Length == 2)
                {
                    account.Chanel = info[0];
                    account.ServerID = "S" + info[1];
                    return account;
                }
                else
                {
                    Console.WriteLine("查找账户信息时出错，原始数据：");
                    PrintDataConsole(datas, length);
                }
            }
            return null;
        }

        //建立一个tabpage，用于显示此角色的游戏信息
        private void AddPage(ConnectionMap map)
        {
            this.tabControl1.TabPages.Add(map.GetHashCode().ToString(), map.Character.Name);
            TabPage page = this.tabControl1.TabPages[map.GetHashCode().ToString()];
            page.Tag = map;//用于键
            RichTextBox txtUserMessage = null;

            if (characterTxtboxMap.ContainsKey(map.Account))
            {
                txtUserMessage = ((RichTextBox)characterTxtboxMap[map.Account]);
            }
            else
            {
                txtUserMessage = new RichTextBox();
                txtUserMessage.BackColor = System.Drawing.Color.Black;
                txtUserMessage.Dock = System.Windows.Forms.DockStyle.Fill;
                txtUserMessage.ForeColor = System.Drawing.Color.White;
                txtUserMessage.Location = new System.Drawing.Point(3, 3);
                txtUserMessage.Name = map.Character.Name + "Message";
                txtUserMessage.Size = new System.Drawing.Size(583, 294);
                txtUserMessage.TabIndex = 0;

                characterTxtboxMap.Add(map.Account, txtUserMessage);//建立角色名和文本框的映射
            }

            page.Controls.Add(txtUserMessage);
            txtUserMessage.Text = map.Character.Name + "已登录\r\n";
        }

        //消息处理
        protected override void DefWndProc(ref Message m)
        {
            string message = "";
            ProcessMessage.ReadMessage(ref m, ref message);
            if (!string.IsNullOrEmpty(message))
            {
                string[] code = message.Split(new char[] { '\t' }, StringSplitOptions.RemoveEmptyEntries);
                if (code.Length > 0)
                {
                    switch (code[0])
                    {
                        case "Start":
                            Log("客户端已启动->" + code[1]);
                            break;
                        case "Login":
                            if (code[1] == "true")//成功登录
                            {
                                Log(code[2]);
                            }
                            else//登录失败，可能账户密码错误
                            {
                                Log(code[2]);
                            }
                            break;
                        case "Logout":
                            Log("账户已退出->" + code[1]);
                            break;
                    }
                }
            }
            base.DefWndProc(ref m);
        }

        #region 事件
        //显示客户端
        private void btnShowClient_Click(object sender, EventArgs e)
        {
            ConnectionMap map = this.tabControl1.SelectedTab.Tag as ConnectionMap;
            if (map != null)
            {
                Account account = map.Account;
                if (account != null)
                {
                    if (this.btnShowClient.Text == "显示客户端")
                    {
                        ProcessMessage.SendMessage(loginFormDict[account].MainWindowTitle, "NeedShow");//发送显示命令给客户端
                        this.btnShowClient.Text = "隐藏客户端";
                    }
                    else
                    {
                        ProcessMessage.SendMessage(loginFormDict[account].MainWindowTitle, "NeedHide");//发送显示命令给客户端
                        this.btnShowClient.Text = "显示客户端";
                    }
                }
            }
        }

        //重新开始所有任务
        private void btnRestart_Click(object sender, EventArgs e)
        {
            ConnectionMap map = this.tabControl1.SelectedTab.Tag as ConnectionMap;
            if (map != null)
            {
                map.Operationer.RestartAll();
            }
        }

        //终止所有任务
        private void btnStopAll_Click(object sender, EventArgs e)
        {
            ConnectionMap map = this.tabControl1.SelectedTab.Tag as ConnectionMap;
            if (map != null)
            {
                map.Operationer.StopAll(true);
            }
        }

        //启动客户端，用于启动之前关闭的客户端
        private void btnStartClient_Click(object sender, EventArgs e)
        {
            if (this.btnStartClient.Text == "启动客户端")
            {
                ConnectionMap map = this.tabControl1.SelectedTab.Tag as ConnectionMap;
                if (map != null)
                {
                    Account account = map.Account;
                    if (account != null)
                    {
                        if (!this.loginFormDict.ContainsKey(account))
                        {
                            Log("账户：" + account.Username + " 开始登录...");
                            Process p = new Process();
                            //助手窗口标题，账户，密码，角色名，平台，服务器编号
                            p.StartInfo = new ProcessStartInfo("Client.exe", this.Text + " " + account.Username + " " + account.Password + " " + account.Character.Name + " " + account.Chanel + " " + account.ServerID);
                            p.Start();
                            loginFormDict.Add(account, p);
                        }
                    }
                }
                this.btnStartClient.Text = "关闭客户端";
            }
            else
            {

                this.btnStartClient.Text = "启动客户端";
            }
        }

        //刷新客户端，重新登录
        private void btnReflush_Click(object sender, EventArgs e)
        {
            ConnectionMap map = this.tabControl1.SelectedTab.Tag as ConnectionMap;
            if (map != null)
            {
                Account account = map.Account;
                if (account != null)
                {
                    if (this.loginFormDict.ContainsKey(account))
                    {
                        ProcessMessage.SendMessage(this.loginFormDict[account].MainWindowTitle, "ReLogin");
                    }
                }
            }
        }


        //账户管理
        private void 账户管理ToolStripMenuItem_Click(object sender, EventArgs e)
        {
            new AccountForm().ShowDialog();
        }

        //暂停自动游戏
        private void menuItemPauseAutoGame_Click(object sender, EventArgs e)
        {
            ConnectionMap map = this.tabControl1.SelectedTab.Tag as ConnectionMap;
            if (map != null)
            {
                if (this.btnPauseAutoGame.Text == "暂停自动游戏")
                {
                    map.Operationer.Pause();
                    this.btnPauseAutoGame.Text = "继续自动游戏";
                }
                else
                {
                    map.Operationer.Continue();
                    this.btnPauseAutoGame.Text = "暂停自动游戏";
                }
            }
        }

        //停止当前自动游戏流程，进行下一个流程
        private void btnStopCurrentAutoGame_Click(object sender, EventArgs e)
        {
            ConnectionMap map = this.tabControl1.SelectedTab.Tag as ConnectionMap;
            if (map != null)
            {
                map.Operationer.StopCurrent();
            }
        }

        //开始自动登录
        private void btnAutoLogin_Click(object sender, EventArgs e)
        {
            Thread thread = new Thread(new ParameterizedThreadStart(StartLoginForm));
            thread.Start();
        }

        //关闭窗口时
        private void MainForm2_FormClosing(object sender, FormClosingEventArgs e)
        {
            if (e.CloseReason == CloseReason.UserClosing)
            {
                this.Hide();
                e.Cancel = true;
            }
        }

        //双击通知图标显示主窗口
        private void notifyIcon1_DoubleClick(object sender, EventArgs e)
        {
            this.Show();
            BringToFront();
        }

        //退出程序
        private void 退出ToolStripMenuItem_Click(object sender, EventArgs e)
        {
            foreach (Account account in Manager.AccountList)
            {
                ConnectionMap map = Manager.GetMapByAccount(account);
                if (map != null)
                {
                    map.Operationer.StopAll();
                    map.GameClientConnection.Close();
                    map.GameServerConnection.Close();
                }
            }
            Application.Exit();
        }

        //改变菜单文本
        private void tabControl1_SelectedIndexChanged(object sender, EventArgs e)
        {
            try
            {
                if (this.tabControl1.SelectedTab.Text == "系统")
                {
                    this.btnPauseAutoGame.Enabled = false;
                    this.btnStopCurrentAutoGame.Enabled = false;
                    this.btnReflush.Enabled = false;
                    this.btnRestart.Enabled = false;
                    this.btnShowClient.Enabled = false;
                    this.btnStartClient.Enabled = false;
                    this.btnStopAll.Enabled = false;
                    return;
                }
                else
                {
                    this.btnPauseAutoGame.Enabled = true;
                    this.btnStopCurrentAutoGame.Enabled = true;
                    this.btnReflush.Enabled = true;
                    this.btnRestart.Enabled = true;
                    this.btnShowClient.Enabled = true;
                    this.btnStartClient.Enabled = true;
                    this.btnStopAll.Enabled = true;
                }

                ConnectionMap map = this.tabControl1.SelectedTab.Tag as ConnectionMap;
                GameConfig config = Manager.GetConfig(map.Account);
                if (config.WindowState == ClientWindowState.Hide)//当客户端设置为隐藏时
                {
                    this.btnShowClient.Enabled = true;
                }
                if (map.Operationer.Paused)
                {
                    this.btnPauseAutoGame.Text = "继续自动游戏";
                }
                else
                {
                    this.btnPauseAutoGame.Text = "暂停自动游戏";
                }
            }
            catch (Exception ex)
            {
                Console.WriteLine("出错了：");
                Tools.PrintException(ex);
            }
        }

        private void MainForm_Load(object sender, EventArgs e)
        {
            //Thread thread = new Thread(new ParameterizedThreadStart(StartLoginForm));
            //thread.Start();
        }
        #endregion

        //发送给客户端
        private void button1_Click(object sender, EventArgs e)
        {
            if (this.textBox1.Text == "")
            {
                return;
            }
            string[] data = this.textBox1.Text.Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries);
            List<byte> byteData = new List<byte>();
            byte num = 0;
            foreach (string s in data)
            {
                if (byte.TryParse(s, NumberStyles.AllowHexSpecifier, null, out num))
                {
                    byteData.Add(num);
                }
            }
            var array = byteData.ToArray();
            TcpHelper.Forward(sendClientFrom8001Tcp, array, array.Length);
        }

        //发送给服务端
        private void button2_Click(object sender, EventArgs e)
        {
            if (this.textBox1.Text == "")
            {
                return;
            }

            TcpClient client = null;
            switch (txtPort.Text)
            {
                case "8000":
                    client = sendServer8000Tcp;
                    break;
                case "8001":
                    client = sendServer8001Tcp;
                    break;
                case "8010":
                    client = sendServer8010Tcp;
                    break;
                default: return;
            }

            string[] data = this.textBox1.Text.Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries);
            List<byte> byteData = new List<byte>();
            byte num = 0;
            foreach (string s in data)
            {
                if (byte.TryParse(s, NumberStyles.AllowHexSpecifier, null, out num))
                {
                    byteData.Add(num);
                }
            }
            var array = byteData.ToArray();
            TcpHelper.Forward(client, array, array.Length);
        }

        private void button3_Click(object sender, EventArgs e)
        {
            this.textBox1.Text = "";
        }
    }

    /// <summary>
    /// 用于异步数据传送的状态对象
    /// </summary>
    class StateObject
    {
        TcpClient client;

        public TcpClient Client
        {
            get { return client; }
            set { client = value; }
        }
        public TcpClient Server { get; set; }
        public int Port { get; set; }

        byte[] buffer;

        public byte[] Buffer
        {
            get { return buffer; }
        }

        public StateObject(TcpClient client)
        {
            buffer = new byte[1024];
            this.client = client;
        }

        public StateObject(TcpClient client, TcpClient server)
        {
            buffer = new byte[1024];
            this.client = client;
            this.Server = server;
        }

        public StateObject(TcpClient client, TcpClient server, int port)
            : this(client, server)
        {
            this.Port = port;
        }

        public StateObject()
        {
            buffer = new byte[1024];
        }
    }

    class ListenerStateObject
    {
        public int Port { get; set; }
        public TcpListener Listener { get; set; }
        public AsyncCallback ClientDataCallback { get; set; }
        public AsyncCallback ServerDataCallback { get; set; }
    }
}
